﻿using System;
using System.Collections.Generic;
using System.Data;
using System.Linq;
using System.Linq.Expressions;

namespace SailHero.Soft.FrameWork.DAO.Contracts
{
    /// <summary>
    /// 数据持久化统一接口
    /// </summary> 
    public interface IRepository<TEntity>
    {
        /// <summary>
        /// 获取IQueryable
        /// </summary>
        /// <returns>IQueryable</returns>
        IQueryable<TEntity> GetQuery();

        /// <summary>
        /// 根据条件获取IQueryable
        /// </summary>
        /// <param name="predicate">查询条件表达式</param>
        /// <returns>IQueryable</returns>
        IQueryable<TEntity> GetQuery(Expression<Func<TEntity, bool>> predicate);

        /// <summary>
        /// 根据主键属性得到实体
        /// </summary>
        /// <param name="objectId">主键属性值</param>
        /// <returns>实体</returns>
        TEntity Get(object objectId);

        /// <summary>
        /// 更新
        /// </summary>
        /// <typeparam name="TEntity"></typeparam>
        /// <param name="source"></param>
        /// <param name="New"></param>
        /// <param name="ignores"></param>
        void UpdateRef<TEntity>(TEntity source, ref TEntity New, params string[] ignores);

        /// <summary>
        /// 根据条件获取唯一的实体
        /// </summary>
        /// <param name="predicate">查询条件表达式</param>
        /// <returns>实体</returns>
        TEntity SingleOrDefault(Expression<Func<TEntity, bool>> predicate);

        /// <summary>
        /// 根据条件获取第一条实体
        /// </summary>
        /// <param name="predicate">查询条件表达式</param>
        /// <returns>实体</returns>
        TEntity FirstOrDefault(Expression<Func<TEntity, bool>> predicate);

        /// <summary>
        /// 根据条件获取列表
        /// </summary>
        /// <param name="predicate">查询条件表达式</param>
        /// <returns>实体列表</returns>
        IEnumerable<TEntity> GetList(Expression<Func<TEntity, bool>> predicate);
        /// <summary>
        /// 根据条件获取列表
        /// </summary>
        /// <returns>实体列表</returns>
        IEnumerable<TEntity> GetAllList();
        /// <summary>
        /// 根据条件获取分页列表
        /// </summary>
        /// <param name="predicate">查询条件表达式</param>
        /// <param name="orderBy">排序字段</param>
        /// <param name="ascending">是否顺序</param>
        /// <param name="pageIndex">页索引</param>
        /// <param name="pageSize">页大小</param>
        /// <returns>实体分页列表</returns>
        PagedList<TEntity> GetPagedList(Expression<Func<TEntity, bool>> predicate, string orderBy, bool ascending,
                                        int pageIndex, int pageSize);

        /// <summary>
        /// 新增实体
        /// </summary>
        /// <param name="entity">实体</param>
        void Add(TEntity entity);


        /// <summary>
        /// 删除实体
        /// </summary>
        /// <param name="entity">实体</param>
        void Delete(TEntity entity);

        /// <summary>
        /// 根据条件删除
        /// </summary>
        /// <param name="predicate">查询条件表达式</param>
        void Delete(Expression<Func<TEntity, bool>> predicate);

        /// <summary>
        /// 获取总数
        /// </summary>
        /// <returns>总数</returns>
        int Count();

        /// <summary>
        /// 根据条件获取总数
        /// </summary>
        /// <param name="predicate">查询条件表达式</param>
        /// <returns>总数</returns>
        int Count(Expression<Func<TEntity, bool>> predicate);
        /// <summary>
        /// 根据存储过程名及参数获取数据 
        /// </summary>
        /// <param name="sp">存储过程名</param>
        /// <returns>存储过程返回的数据</returns>
        IEnumerable<TEntity> GetDataBySp(string sp);
        /// <summary>
        /// 工作单元
        /// </summary>
        IUnitOfWork UnitOfWork { get; }
    }
}